package com.wxj.bank.storage.service.impl;

import com.mongodb.client.result.DeleteResult;
import com.wxj.bank.module.modle.criteria.OrderBy;
import com.wxj.bank.module.modle.criteria.Where;
import com.wxj.bank.module.utils.MongoQueryUtils;
import com.wxj.bank.storage.service.IMongoService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.aggregation.Aggregation;
import org.springframework.data.mongodb.core.aggregation.AggregationResults;
import org.springframework.data.mongodb.core.mapreduce.MapReduceResults;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.Update;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;

/**
 * @author shengtao
 * @Description: mongodb工具类
 * @date 2019/02/01 13:15
 */
@Service
public class MongoServiceImpl implements IMongoService{

    private static final Logger LOGGER = LoggerFactory.getLogger(MongoServiceImpl.class);

    @Autowired
    private MongoTemplate mongoTemplate;

    @Override
    public void insert(Object obj, String collectionName) {
        try {
            mongoTemplate.insert(obj,collectionName);
        }catch (RuntimeException var1){
            LOGGER.error(String.format("Save 保存实体[%s]异常，", new Object[]{collectionName}), var1);
            throw var1;
        }
    }

    @Override
    public void insertAll(Collection<?> objs, String collectionName) {
        try {
            mongoTemplate.insert(objs,collectionName);
        }catch (RuntimeException var2){
            LOGGER.error(String.format("batchSave 批量保存实体[%s]异常，", new Object[]{collectionName}), var2);
            throw var2;
        }
    }

    @Override
    public boolean delete(Object obj, String collectionName) {
        try {
            DeleteResult deleteResult = this.mongoTemplate.remove(obj,collectionName);
            if(deleteResult.getDeletedCount() >= 1){
                return true;
            }
        }catch (RuntimeException var2){
            LOGGER.error(String.format("delete 保存实体[%s]异常，", new Object[]{collectionName}), var2);
        }
        return false;
    }

    @Override
    public long delete(Query query, String collectionName) {
        try{
            DeleteResult deleteResult = this.mongoTemplate.remove(query,collectionName);
            return deleteResult.getDeletedCount();
        }catch (RuntimeException var3){
            LOGGER.error(String.format("delete 批量条件保存实体[%s]异常，", new Object[]{collectionName}), var3);
        }
        return 0;
    }

    @Override
    public void update(Object obj, String collectionName) { //添加覆盖：复写id
        try {
            this.mongoTemplate.save(obj,collectionName);
        }catch (RuntimeException var4){
            LOGGER.error(String.format("update 更新实体[%s]异常，", new Object[]{collectionName}), var4);
            throw var4;
        }
    }

    @Override
    public void updateMulti(Collection<?> objs, String collectionName) {
        Iterator iterator = objs.iterator();
        try {
            while (iterator.hasNext()){
                this.mongoTemplate.save(iterator.next(),collectionName);
            }
        }catch (RuntimeException var5){
            LOGGER.error(String.format("batchUpdate 批量更新实体[%s]异常，", new Object[]{collectionName}), var5);
            throw var5;
        }
    }

    @Override
    public long updateMulti(Query query, Update update, String collectionName) {
        try {
            this.mongoTemplate.updateMulti(query,update,collectionName);
        }catch (RuntimeException var5){
            LOGGER.error(String.format("update 批量条件修改实体[%s]异常，", new Object[]{collectionName}), var5);
        }
        return 0;
    }

    @Override
    public long count(Query query, String collectionName) {
        try {
            return this.mongoTemplate.count(query,collectionName);
        }catch (RuntimeException var5){
            LOGGER.error(String.format("count 条件查询数量[%s]异常，", new Object[]{collectionName}), var5);
        }
        return 0;
    }

    @Override
    public <T> T findById(String id,Class<T> tClass, String collectionName) {
        return this.mongoTemplate.findById(id,tClass,collectionName);
    }

    @Override
    public long updateMulti(Where[] wheres, Update update, String collectionName) {
        try {
            this.mongoTemplate.updateMulti(MongoQueryUtils.getQuery(wheres),update,collectionName);
        }catch (RuntimeException var5){
            LOGGER.error(String.format("update 批量条件保存实体[%s]异常，", new Object[]{collectionName}), var5);
        }
        return 0;
    }

    @Override
    public long count(Where[] wheres, String collectionName) {
        try {
            return this.mongoTemplate.count(MongoQueryUtils.getQuery(wheres),collectionName);
        }catch (RuntimeException var6){
            LOGGER.error(String.format("count 条件查询数[%s]异常，", new Object[]{collectionName}), var6);
        }
        return 0;
    }

    @Override
    public <T> List<T> findAll(Class<T> tClass, String collectionName) {
        return this.mongoTemplate.findAll(tClass,collectionName);
    }

    @Override
    public <T> List<T> find(Where[] wheres, OrderBy[] orders, int skip, int limit, Class<T> tClass, String collectionName) {
        return this.mongoTemplate.find(MongoQueryUtils.getQuery(wheres,orders,skip,limit),tClass,collectionName);
    }

    @Override
    public <T> List<T> aggregate(Aggregation aggregation, String collectionName, Class<T> tClass) {
        try {
            AggregationResults<T> results = this.mongoTemplate.aggregate(aggregation,collectionName,tClass);
            return results.getMappedResults();
        }catch (RuntimeException var7){
            LOGGER.error(String.format("aggregate 条件聚合查询[%s]异常，", new Object[]{collectionName}), var7);
        }
        return null;
    }

    @Override
    public <T> List<T> mapReduce(String collectionName, String map, String reduce, Class<T> tClass) {
        try {
            MapReduceResults<T> reduceResults = this.mongoTemplate.mapReduce(collectionName,map,reduce,tClass);
            List<T> results = new ArrayList<>();
            Iterator<T> iterator = reduceResults.iterator();
            while (iterator.hasNext()){
                results.add(iterator.next());
            }
        }catch (RuntimeException var8){
            LOGGER.error(String.format("map-reduce 查询[%s]异常，", new Object[]{collectionName}), var8);
        }
        return null;
    }


}
